<!--
 * @author luguoxiang
 * @date 2022/9/17
 * 开源项目：https://gitee.com/lgx1992/lg-soar 求star！请给我star！请帮我点个star！
-->
<template>
  <edit-container ref="editContainerRef" header="代码生成" width="var(--app-main-width)" @open="onopen">
    <t-form autocomplete="on">
      <lg-grid :horizontal="12">
        <t-form-item label="业务描述">
          <t-input v-model.trim="model.comment" tips="如：用户、角色、商品等业务名称" />
        </t-form-item>
        <t-form-item label="接口路径">
          <t-input v-model.trim="model.apiPath" tips="控制器路径" />
        </t-form-item>
        <t-form-item label="表名前缀">
          <t-input
            v-model.trim="model.tablePrefix"
            tips="生成类名忽略前缀"
            @input="tablePrefixChange(model.tablePrefix)"
          />
        </t-form-item>
        <t-form-item label="类名">
          {{ model.modelName }}
        </t-form-item>
        <t-form-item label="模板">
          <t-select
            v-model.trim="model.template"
            :options="templateList"
            tips="后端继承的类"
            @change="templateChange"
          />
        </t-form-item>
        <t-form-item label="作者">
          <t-input v-model.trim="model.author" />
        </t-form-item>
        <t-form-item label="输出目录">
          <t-input v-model.trim="model.outputDir" />
        </t-form-item>
      </lg-grid>
      <t-tabs placement="left" theme="card" default-value="java">
        <t-tab-panel value="java" label="java" :destroy-on-hide="false">
          <lg-grid :horizontal="12">
            <t-form-item label="包名">
              <t-input v-model.trim="javaConfig.parentPackages" />
            </t-form-item>
          </lg-grid>
          <lg-table
            ref="javaTableRef"
            :schema="javaColumns"
            :data="javaConfig.fields"
            v-bind="tableProps"
            :selection="false"
          ></lg-table>
        </t-tab-panel>
        <t-tab-panel value="web" label="web" :destroy-on-hide="false">
          <lg-grid :horizontal="12">
            <t-form-item label="包名">
              <t-input v-model.trim="webConfig.directory" />
            </t-form-item>
          </lg-grid>
          <lg-table
            ref="webTableRef"
            :schema="webColumns"
            :data="webConfig.fields"
            v-bind="tableProps"
          >
            <template #actionbar="{ row }">
              <a @click="openModal(row)">编辑</a>
            </template>
            <template #table="{ row }">
              <t-checkbox v-model="row.table" />
            </template>
            <template #search="{ row }">
              <t-checkbox v-model="row.search" />
            </template>
            <template #form="{ row }">
              <t-checkbox v-model="row.form" />
            </template>
            <template #detail="{ row }">
              <t-checkbox v-model="row.detail" />
            </template>
          </lg-table>
        </t-tab-panel>
      </t-tabs>
    </t-form>
    <template #footer>
      <t-button v-loading="loading" @click="ok">确定</t-button>
      <t-button variant="outline" @click="editContainerRef.close()"> 取消 </t-button>
    </template>
  </edit-container>
  <lg-modal ref="modalRef" @ok="modalOk">
    <!--    <lg-json-editor v-model:value="json" />-->
  </lg-modal>
</template>

<script setup lang="ts">
import { nextTick, reactive, ref } from 'vue';
import { LgGrid, LgTable, LgTableProps, message, toHump } from '@/soar';
import { EditContainer } from '@/components';
import { generate, tableInfo } from './api';
import { javaColumns, jsonType, soarQueryField, templates, webColumns } from './config';

const tableProps: LgTableProps = {
  index: true,
  selection: true,
  toolbar: false,
  alert: false,
  tableProps: {
    bordered: true,
    rowKey: 'name',
  },
};

const editContainerRef = ref();
const javaTableRef = ref();
const webTableRef = ref();
const loading = ref(false);
const options = reactive({
  javaBasePath: [],
  webBasePath: [],
});

const modalRef = ref();
const templateList = ref(templates);
const model = ref({
  tableName: '',
  modelName: '',
});
const javaConfig = ref({
  parentPackages: '',
  fields: [],
});
const webConfig = ref({
  directory: '',
  fields: [],
});
const json = ref('');

function tablePrefixChange(e: any) {
  e = toHump(model.value.tableName.replace(e, ''));
  model.value.modelName = e.slice(0, 1).toUpperCase() + e.slice(1);
}

let fields = [];

/**
 * 当页面打开
 * @param params
 */
function onopen(params: any) {
  tableInfo(params.TABLE_NAME).then((res: any) => {
    model.value = res;
    javaConfig.value = res.javaConfig;
    webConfig.value = res.webConfig;
    fields = res.javaConfig.fields;
    fields.forEach((x) => {
      x.jsonType = '正常';
      x.soarQueryField = '正常';
      x.transType = '无';
    });
    javaConfig.value.fields = fields.filter((x) => x.enabled);
  });
}

/**
 * 点击确定时
 */
function ok() {
  const javaFields = javaConfig.value.fields.map((x) => {
    const annotations = [...(x.annotations || [])];
    if (x.jsonType !== '正常') {
      annotations.push(jsonType.find((y) => y.value === x.jsonType).annotation);
    }
    if (x.soarQueryField !== '正常') {
      annotations.push(soarQueryField.find((y) => y.value === x.soarQueryField).annotation);
    }
    return {
      name: x.name,
      propertyName: x.propertyName,
      javaType: x.javaType,
      comment: x.comment,
      pk: x.pk,
      nullable: x.nullable,
      enabled: x.enabled,
      annotations,
    };
  });
  const webFields = webConfig.value.fields.map((x) => {
    return {
      name: x.name,
      field: x.field,
      label: x.label,
      dataType: x.dataType,
      params: x.params,
      pk: x.pk,
      nullable: x.nullable,
      enabled: x.enabled,
      table: x.table === false ? false : null,
      search: x.search === false ? false : null,
      form: x.form === false ? false : null,
      detail: x.detail === false ? false : null,
    };
  });
  generate({
    ...model.value,
    javaConfig: {
      ...javaConfig.value,
      fields: javaFields,
    },
    webConfig: {
      ...webConfig.value,
      fields: webFields,
    },
  })
    .then(() => {
      // editContainerRef.value.close();
    })
    .finally(() => {
      loading.value = false;
    });
  loading.value = true;
}

/**
 * 打开json编辑弹窗
 * @param row
 */
function openModal(row: any) {
  row = { ...row };
  delete row.name;
  json.value = JSON.stringify(row, null, 2);
  modalRef.value.open();
}

/**
 * json编辑确定
 */
function modalOk() {
  try {
    const jsonValue = JSON.parse(json.value);
    for (const k in jsonValue) {
    }
    modalRef.value.close();
  } catch (e) {
    console.error(e);
    message.error('json格式书写错误');
  }
}

/**
 * 切换模板
 * @param v
 */
function templateChange(v: any) {
  const template = templateList.value[v];
  const columns = source.java.map((x: any) => x.propertyName);
  source.template = template;
  template.columns.forEach((x: any) => {
    columns.splice(columns.indexOf(x), 1);
  });
  columns.splice(columns.indexOf('id'), 1);

  // 后端配置数据
  javaData.value = source.java.filter((x: any) => template.columns.indexOf(x.name) === -1);
  // 前端配置数据
  webData.value = source.web;

  nextTick(() => {
    javaTableRef.value.select(javaData.value.map((x) => x.name));
    webTableRef.value.select(
      webData.value.filter((x) => !(x.name === 'id' || template.columns.indexOf(x.name) !== -1)).map((x) => x.name),
    );
  });
}

defineExpose({
  open(params: any) {
    editContainerRef.value.open(params);
  },
});
</script>

<style scoped lang="less">
.t-drawer__body {
  color: red;
}
:deep(.t-drawer__body) {
  height: 100%;
  display: flex;
  flex-direction: column;
  .t-tabs {
    flex: 1;
  }
  .t-tabs__content {
    height: 100%;
  }
  .t-tab-panel {
    height: 100%;
    display: flex;
    flex-direction: column;
  }
  .lg-table {
    flex: 1;
  }
}
.gl-tabs-auto-h {
  border-top: 1px solid #ddd;
  padding-top: 16px;
}
.t-form {
  display: flex;
  flex-direction: column;
  .t-tabs {
    flex: 1;
    :deep(.t-tabs__content){
      height: 100%;
    }
    :deep(.t-tab-panel:not(.t-is-hidden)) {
      height: 100%;
      display: flex;
      flex-direction: column;
    }
  }
}
</style>
